package main

import "fmt"
/*
	最佳买卖股票时机含冷冻期
给定一个整数数组，其中第 i 个元素代表了第 i 天的股票价格 。​
设计一个算法计算出最大利润。在满足以下约束条件下，你可以尽可能地完成更多的交易（多次买卖一支股票）:
你不能同时参与多笔交易（你必须在再次购买前出售掉之前的股票）。
卖出股票后，你无法在第二天买入股票 (即冷冻期为 1 天)。

示例:
输入: [1,2,3,0,2]
输出: 3
解释: 对应的交易状态为: [买入, 卖出, 冷冻期, 买入, 卖出]
 */

/*
 动态规划   每天有三种状态
1. 手上有一只股票
2. 手上没有股票 且处于冷冻期（处于冷冻期指的是在第i天结束之后的状态。也就是说：如果第i天结束之后处于冷冻期，那么第i+1天无法买入股票）
3. 手上没有股票 且不属于冷冻期

对于情况一 要么保持该股票（说明前一天有股票） 要么是今天刚买的（前一天手上没有股票 且不属于冷冻期）
	dp[i][0] = max(dp[i - 1][0], dp[i - 1][2] - prices[i])
对于情况二 当天卖出了股票（说明前一天有一张股票）
	dp[i][1] = dp[i - 1][0] + prices[i]
对于情况三 当天没有任何操作（手上没有股票）
	dp[i][2] = max(dp[i - 1][1], dp[i - 1][2])

*/
func maxProfit(prices []int) int {
	length := len(prices)
	if length < 2 {
		return 0
	}
	dp := make([][3]int, length)
	max := func(x, y int) int {
		if x > y {
			return x
		}
		return y
	}
	// dp[i][0]: 手上持有股票的最大收益
	// dp[i][1]: 手上不持有股票，并且处于冷冻期中的累计最大收益
	// dp[i][2]: 手上不持有股票，并且不在冷冻期中的累计最大收益
	dp[0][0] = -prices[0]  // 边界条件
	for i := 1; i < length; i++ {
		dp[i][0] = max(dp[i - 1][0], dp[i - 1][2] - prices[i])
		dp[i][1] = dp[i - 1][0] + prices[i]
		dp[i][2] = max(dp[i - 1][1], dp[i - 1][2])
	}
	return max(dp[length- 1][1], dp[length - 1][2])
}

func main() {
	fmt.Println(maxProfit([]int{1,2,3,0,2}))
}
